package com.shijie.log.util;

import com.shijie.log.comparator.FieldComparator;
import com.shijie.log.comparator.FieldComparatorUtil;
import com.shijie.log.formatter.ValueFormatter;
import com.shijie.log.recorder.DiffLogRecorder;
import lombok.extern.slf4j.Slf4j;

import java.util.ArrayList;
import java.util.List;

@Slf4j
public class FieldDiffLogUtil {

    private final List<FieldItem<?>> fieldItems = new ArrayList<>();
    private List<FieldItem<?>> changedFieldItems;

    private FieldDiffLogUtil() {
    }

    // 多字段入口
    public static FieldDiffLogUtil fieldDiff() {
        return new FieldDiffLogUtil();
    }

    // 单字段入口
    public static <T> FieldDiffLogUtil fieldDiff(String key, T oldVal, T newVal, FieldComparator<T> comparator, ValueFormatter formatter) {
        FieldDiffLogUtil util = new FieldDiffLogUtil();
        util.fieldItems.add(new FieldItem<>(key, oldVal, newVal, comparator, formatter));
        util.checkFieldDiff();
        return util;
    }

    // 多字段添加（默认/指定对比器）
    public FieldDiffLogUtil addField(String fieldName, Object oldVal, Object newVal) {
        fieldItems.add(new FieldItem<>(fieldName, oldVal, newVal, FieldComparatorUtil.DEFAULT_COMPARATOR, ValueFormatter.DEFAULT_FORMATTER));
        return this;
    }

    // 多字段添加
    public <T> FieldDiffLogUtil addField(String fieldName, T oldVal, T newVal, FieldComparator<T> comparator, ValueFormatter formatter) {
        fieldItems.add(new FieldItem<>(fieldName, oldVal, newVal, comparator, formatter));
        return this;
    }

    public FieldDiffLogUtil checkFieldDiff() {
        this.changedFieldItems = filterChangedFields();
        return this;
    }

    // ---------------------- 多字段记录（支持格式化器） ----------------------
    public int batchRecord(DiffLogRecorder<FieldItem<?>> recorder) {
        if (changedFieldItems == null) {
            this.changedFieldItems = filterChangedFields();
        }
        int changeCount = changedFieldItems.size();
        if (changeCount > 0) {
            DiffLogRecordUtil.batchRecord(recorder, changedFieldItems);
        }
        return changeCount;
    }

    // ---------------------- 单字段记录（支持格式化器） ----------------------
    public int record(DiffLogRecorder<FieldItem<?>> recorder) {
        if (changedFieldItems == null) {
            this.changedFieldItems = filterChangedFields();
        }
        int changeCount = changedFieldItems.size();
        if (changeCount > 0) {
            FieldItem<?> first = changedFieldItems.getFirst();
            DiffLogRecordUtil.record(recorder, first.fieldName(), first.oldVal(), first.newVal(), first.formatter());
        }
        return changeCount;
    }

    // 私有筛选方法（调用FieldItem内部isChanged()）
    private List<FieldItem<?>> filterChangedFields() {
        return fieldItems.stream()
                .filter(FieldItem::isChanged)
                .toList();
    }

    // ---------------------- 内部封装类（字段信息+对比逻辑） ----------------------
    public record FieldItem<T>(String fieldName, T oldVal, T newVal, FieldComparator<T> comparator,
                               ValueFormatter formatter) {
        public boolean isChanged() {
            return !comparator.compare(oldVal, newVal);
        }
    }
}